<?php

/**
 * This file is part of PHPPresentation - A pure PHP library for reading and writing
 * presentations documents.
 *
 * PHPPresentation is free software distributed under the terms of the GNU Lesser
 * General Public License version 3 as published by the Free Software Foundation.
 *
 * For the full copyright and license information, please read the LICENSE
 * file that was distributed with this source code. For the full list of
 * contributors, visit https://github.com/PHPOffice/PHPPresentation/contributors.
 *
 * @see        https://github.com/PHPOffice/PHPPresentation
 *
 * @license     http://www.gnu.org/licenses/lgpl.txt LGPL version 3
 */

declare(strict_types=1);

namespace PhpOffice\PhpPresentation\Tests\Writer\ODPresentation;

use PhpOffice\PhpPresentation\Exception\FileNotFoundException;
use PhpOffice\PhpPresentation\Shape\Drawing;
use PhpOffice\PhpPresentation\Slide\Background\Image;
use PhpOffice\PhpPresentation\Tests\PhpPresentationTestCase;

/**
 * Test class for PhpOffice\PhpPresentation\Writer\ODPresentation\Manifest.
 *
 * @coversDefaultClass \PhpOffice\PhpPresentation\Writer\ODPresentation\Manifest
 */
class MetaInfManifestTest extends PhpPresentationTestCase
{
    protected $writerName = 'ODPresentation';

    public function testDrawing(): void
    {
        $oShape = $this->oPresentation->getActiveSlide()->createDrawingShape();
        $oShape->setPath(PHPPRESENTATION_TESTS_BASE_DIR . '/resources/images/PhpPresentationLogo.png');

        $element = '/manifest:manifest/manifest:file-entry[5]';
        $this->assertZipXmlElementExists('META-INF/manifest.xml', $element);
        $this->assertZipXmlAttributeStartsWith('META-INF/manifest.xml', $element, 'manifest:full-path', 'Pictures/PhpPresentationLogo');
        $this->assertZipXmlAttributeEndsWith('META-INF/manifest.xml', $element, 'manifest:full-path', '.png');
        // Invalid because `draw:image` has attribute `loext:mime-type`
        $this->assertIsSchemaOpenDocumentNotValid('1.2');
    }

    public function testDrawingException(): void
    {
        $path = PHPPRESENTATION_TESTS_BASE_DIR . '/resources/images/filedoesntexist.png';
        $this->expectException(FileNotFoundException::class);
        $this->expectExceptionMessage(sprintf(
            'The file "%s" doesn\'t exist',
            $path
        ));

        $oShape = $this->oPresentation->getActiveSlide()->createDrawingShape();
        $oShape->setPath($path, false);

        $this->writePresentationFile($this->oPresentation, 'ODPresentation');
    }

    public function testMemoryDrawing(): void
    {
        $oSlide = $this->oPresentation->getActiveSlide();
        $oShape = new Drawing\Gd();

        $gdImage = @imagecreatetruecolor(140, 20);
        $textColor = imagecolorallocate($gdImage, 255, 255, 255);
        imagestring($gdImage, 1, 5, 5, 'Created with PhpPresentation', $textColor);
        $oShape->setImageResource($gdImage)->setRenderingFunction(Drawing\Gd::RENDERING_JPEG)->setMimeType(Drawing\Gd::MIMETYPE_DEFAULT);
        $oSlide->addShape($oShape);

        $element = '/manifest:manifest/manifest:file-entry[5]';
        $this->assertZipXmlElementExists('META-INF/manifest.xml', $element);
        $this->assertZipXmlAttributeEquals('META-INF/manifest.xml', $element, 'manifest:full-path', 'Pictures/' . $oShape->getIndexedFilename());
        // Invalid because `draw:image` has attribute `loext:mime-type`
        $this->assertIsSchemaOpenDocumentNotValid('1.2');
    }

    public function testDrawingZip(): void
    {
        $oSlide = $this->oPresentation->getActiveSlide();

        $oShape = new Drawing\ZipFile();
        $oShape->setPath('zip://' . PHPPRESENTATION_TESTS_BASE_DIR . DIRECTORY_SEPARATOR . 'resources' . DIRECTORY_SEPARATOR . 'files' . DIRECTORY_SEPARATOR . 'Sample_01_Simple.pptx#ppt/media/phppowerpoint_logo1.gif');
        $oSlide->addShape($oShape);

        $element = '/manifest:manifest/manifest:file-entry[5]';
        $this->assertZipXmlElementExists('META-INF/manifest.xml', $element);
        $this->assertZipXmlAttributeEquals('META-INF/manifest.xml', $element, 'manifest:full-path', 'Pictures/' . $oShape->getIndexedFilename());
        // Invalid because `draw:image` has attribute `loext:mime-type`
        $this->assertIsSchemaOpenDocumentNotValid('1.2');
    }

    public function testDrawingZipException(): void
    {
        $path = PHPPRESENTATION_TESTS_BASE_DIR . DIRECTORY_SEPARATOR . 'resources' . DIRECTORY_SEPARATOR . 'files' . DIRECTORY_SEPARATOR . 'filedoesntexist.zip';
        $this->expectException(FileNotFoundException::class);
        $this->expectExceptionMessage(sprintf(
            'The file "%s" doesn\'t exist',
            $path
        ));

        $oShape = new Drawing\ZipFile();
        $oShape->setPath('zip://' . $path);
        $this->oPresentation->getActiveSlide()->addShape($oShape);

        $this->writePresentationFile($this->oPresentation, 'ODPresentation');
    }

    public function testDrawingBase64(): void
    {
        $oShape = new Drawing\Base64();
        $oShape->setData('');
        $this->oPresentation->getActiveSlide()->addShape($oShape);

        $element = '/manifest:manifest/manifest:file-entry[5]';
        $this->assertZipXmlElementExists('META-INF/manifest.xml', $element);
        $this->assertZipXmlAttributeEquals('META-INF/manifest.xml', $element, 'manifest:full-path', 'Pictures/' . $oShape->getIndexedFilename());
        // Invalid because `draw:image` has attribute `loext:mime-type`
        $this->assertIsSchemaOpenDocumentNotValid('1.2');
    }

    public function testSlideBackground(): void
    {
        $oBkgImage = new Image();
        $oBkgImage->setPath(PHPPRESENTATION_TESTS_BASE_DIR . '/resources/images/PhpPresentationLogo.png');
        $this->oPresentation->getActiveSlide()->setBackground($oBkgImage);

        $element = '/manifest:manifest/manifest:file-entry[5]';
        $this->assertZipXmlElementExists('META-INF/manifest.xml', $element);
        $this->assertZipXmlAttributeEquals('META-INF/manifest.xml', $element, 'manifest:full-path', 'Pictures/' . str_replace(' ', '_', $oBkgImage->getIndexedFilename((string) 0)));
        $this->assertIsSchemaOpenDocumentValid('1.2');
    }
}
